package com.dna.service.impl;

import java.util.HashSet;
import java.util.List;
import java.util.Set;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.dna.entity.MenuEntity;
import com.dna.entity.UserEntity;
import com.dna.mapper.MenuMapper;
import com.dna.service.MenuService;
import com.google.common.collect.Lists;
import com.google.common.collect.Sets;
import tk.mybatis.mapper.entity.Example;
import tk.mybatis.mapper.entity.Example.Criteria;

@Service
public class MenuServiceImpl implements MenuService {

    @Autowired
    private MenuMapper menuMapper;

    @Override
    public Set<String> queryPerByRoleId(Long roleId) {

        Set<String> perSet = menuMapper.queryPerByRoleId(roleId);

        return perSet;
    }

    @Override
    public List<MenuEntity> queryByUser(UserEntity userEntity) {

        Long roleId = userEntity.getRoleId();
        List<MenuEntity> menuList = buildMenuTree(menuMapper.queryByRoleId(roleId), 0L);

        return menuList;
    }

    public List<MenuEntity> buildMenuTree(List<MenuEntity> list, Long id) {
        List<MenuEntity> subMenuList = Lists.newArrayList();

        for (MenuEntity menu : list) {
            if (id == menu.getParentId()) {
                menu.setChildren(buildMenuTree(list, menu.getId()));
                subMenuList.add(menu);
            }
        }
        return subMenuList;
    }

    @Override
    public List<MenuEntity> queryAll() {

        List<MenuEntity> menuList = buildMenuTree(menuMapper.queryList(), 0L);

        return menuList;
    }

    @Override
    public MenuEntity queryOne(MenuEntity menu) {
        return menuMapper.selectOne(menu);
    }

    @Override
    @Transactional
    public void save(MenuEntity menu) {
        menuMapper.insertSelective(menu);
    }

    @Override
    @Transactional
    public void update(MenuEntity menu) {
        menuMapper.updateByPrimaryKeySelective(menu);
    }

    @Override
    @Transactional
    public void delete(Set<Long> ids) {

        List<MenuEntity> menuList = menuMapper.selectAll();

        Set<Long> menuSet = Sets.newHashSet(ids);
        menuSet = getMenuIds(menuList, ids, menuSet);

        Example example = new Example(MenuEntity.class);
        Criteria criteria = example.createCriteria();
        criteria.andIn("id", menuSet);

        if (menuMapper.deleteByExample(example) > 0) {
            menuMapper.deleRelation(menuSet);
        }

    }

    private Set<Long> getMenuIds(List<MenuEntity> menuList, Set<Long> ids, Set<Long> menuSet) {
        if (ids.isEmpty()) {
            return menuSet;
        }

        Set<Long> startIds = new HashSet<>(ids);

        for (Long id : ids) {
            for (MenuEntity menu : menuList) {
                if (id.intValue() == menu.getParentId().intValue()) {
                    menuSet.add(menu.getId());
                    startIds.add(menu.getId());
                }
            }
            startIds.remove(id);
        }
        return getMenuIds(menuList, startIds, menuSet);
    }

}
